package com.zyfdroid.backupftpserver.ftplets;

import android.content.pm.ApplicationInfo;
import android.content.pm.PackageInfo;
import android.content.pm.PackageManager;

import org.apache.ftpserver.ftplet.FtpFile;

import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;

public class AppContainerFtpFile implements FtpFile {

    private PackageManager pm;

    static HashMap<String,AppPackageFtpFile> namePackageMapping=null;

    public AppContainerFtpFile(PackageManager pm) {
        this.pm = pm;
    }

    @Override
    public String getAbsolutePath() {
        return "/app";
    }

    @Override
    public String getName() {
        return "app";
    }

    @Override
    public boolean isHidden() {
        return false;
    }

    @Override
    public boolean isDirectory() {
        return true;
    }

    @Override
    public boolean isFile() {
        return false;
    }

    @Override
    public boolean doesExist() {
        return true;
    }

    @Override
    public boolean isReadable() {
        return true;
    }

    @Override
    public boolean isWritable() {
        return false;
    }

    @Override
    public boolean isRemovable() {
        return false;
    }

    @Override
    public String getOwnerName() {
        return "rootfs";
    }

    @Override
    public String getGroupName() {
        return "root";
    }

    @Override
    public int getLinkCount() {
        return 1;
    }

    @Override
    public long getLastModified() {
        return 0;
    }

    @Override
    public boolean setLastModified(long l) {
        return false;
    }

    @Override
    public long getSize() {
        return 0;
    }

    @Override
    public Object getPhysicalFile() {
        return null;
    }

    @Override
    public boolean mkdir() {
        return false;
    }

    @Override
    public boolean delete() {
        return false;
    }

    @Override
    public boolean move(FtpFile ftpFile) {
        return false;
    }

    @Override
    public List<? extends FtpFile> listFiles() {
        List<AppPackageFtpFile> files = new ArrayList<>();
        files.addAll(getNamePackageMapping(pm).values());
        return files;
    }

    public static HashMap<String,AppPackageFtpFile> getNamePackageMapping(PackageManager pm){
        if(null==namePackageMapping){
            namePackageMapping = new HashMap<>();
            for (PackageInfo pif : pm.getInstalledPackages(0)) {
                try {
                    if((pif.applicationInfo.flags & ApplicationInfo.FLAG_SYSTEM )== 0) {
                        String packageName = pif.packageName;
                        StringBuilder displayNameBuilder = new StringBuilder();

                        CharSequence appname = null;
                        try {
                            appname = pm.getApplicationLabel(pif.applicationInfo);
                        }catch (Exception ex){}
                        if(null==appname || appname.length()==0){
                            appname=packageName;
                        }
                        displayNameBuilder.append(appname.toString()).append("_");
                        String versionName = pif.versionName;
                        if(versionName==null || versionName.length()==0){
                            versionName ="ver"+ pif.getLongVersionCode();
                        }
                        else{
                            versionName+="("+pif.getLongVersionCode()+")";
                        }
                        displayNameBuilder.append(versionName);
                        int duplicationDetection=0;
                        String finalName="";
                        do{
                            finalName = normalizeFilename(displayNameBuilder.toString())+(duplicationDetection>0 ? "_"+duplicationDetection : "")+".apk";
                            duplicationDetection++;
                        }while (namePackageMapping.containsKey(finalName));
                        AppPackageFtpFile file = new AppPackageFtpFile(pm,finalName,packageName);
                        namePackageMapping.put(finalName,file);
                    }
                } catch (PackageManager.NameNotFoundException ignored) {

                }
            }
        }
        return namePackageMapping;
    }

    public static void disposeFiles(){namePackageMapping=null;}

    private static String normalizeFilename(String before){
        char[] invalidChars = {'/','\\','*','?',':','<','>','|','"'};
        for (int i = 0; i < invalidChars.length; i++) {
            before = before.replace(invalidChars[i],'_');
        }
        return before;
    }

    @Override
    public OutputStream createOutputStream(long l) throws IOException {
        throw  new IOException("👴是目录");
    }

    @Override
    public InputStream createInputStream(long l) throws IOException {
        throw new IOException("👴是目录");
    }
}
